package com.wstuo.common.noticeRule.service;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.Reader;
import java.io.UnsupportedEncodingException;
import java.lang.reflect.InvocationTargetException;
import java.nio.ByteBuffer;
import java.nio.channels.FileChannel;
import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;

import org.apache.commons.beanutils.BeanUtils;
import org.apache.commons.io.FileUtils;
import org.apache.log4j.Logger;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.transaction.annotation.Transactional;

import com.wstuo.common.bpm.dto.FlowTaskDTO;
import com.wstuo.common.config.server.dto.ServerUrlDTO;
import com.wstuo.common.config.server.service.IServerUrlService;
import com.wstuo.common.config.systeminfo.dao.ISystemInfoDAO;
import com.wstuo.common.config.systeminfo.entity.SystemInfo;
import com.wstuo.common.noticeRule.dao.INoticeRuleDAO;
import com.wstuo.common.noticeRule.dto.NoticeInfoDTO;
import com.wstuo.common.noticeRule.dto.NoticeRuleDTO;
import com.wstuo.common.noticeRule.dto.TemplateVariableDTO;
import com.wstuo.common.noticeRule.entity.NoticeRule;
import com.wstuo.common.noticeRule.utils.NoticeType;
import com.wstuo.common.noticemq.NoticeMessageProducer;
import com.wstuo.common.tools.dto.MessageConsumerDTO;
import com.wstuo.common.tools.dto.NoticeSendDTO;
import com.wstuo.common.tools.dto.PushMessageDTO;
import com.wstuo.common.tools.push.PushService;
import com.wstuo.common.tools.service.IEmailService;
import com.wstuo.common.tools.service.IInstantMessageService;
import com.wstuo.common.tools.sms.SMSSenderHelper;
import com.wstuo.common.dto.PageDTO;
import com.wstuo.common.exception.ApplicationException;
import com.wstuo.common.file.csv.CSVReader;
import com.wstuo.common.proxy.service.IProxyService;
import com.wstuo.common.security.dao.IUserDAO;
import com.wstuo.common.security.dto.UserDTO;
import com.wstuo.common.security.dto.UserQueryDTO;
import com.wstuo.common.security.entity.Organization;
import com.wstuo.common.security.entity.User;
import com.wstuo.common.security.service.IUserInfoService;
import com.wstuo.common.security.utils.AppConfigUtils;
import com.wstuo.common.security.utils.AppContext;
import com.wstuo.common.security.utils.FileEncodeUtils;
import com.wstuo.common.util.StringUtils;
import com.wstuo.common.util.TimeUtils;

/**
 * 通知规则Service
 * 
 * @author QXY
 * 
 */
public class NoticeRuleService implements INoticeRuleService {
	private final static Logger LOGGER = Logger
			.getLogger(NoticeRuleService.class);
	private static final String TEMPLATES_FILE_PATH = AppConfigUtils
			.getInstance().getTemplateFilePath();
	public static final String EMAIL_TEMPLATE_STYPE = "email";
	public static final String TITLE_TEMPLATE_STYPE = "title";
	public static final String IM_TEMPLATE_STYPE = "im";
	public static final String SMS_TEMPLATE_STYPE = "sms";
	public static final String PUSH_TEMPLATE_STYPE = "push";
	public static final String REQUEST_MODULE = "request";
	public static final String PROBLE_MODULE = "problem";
	public static final String CHANGE_MODULE = "change";
	public static final String RELEASE_MODULE = "release";
	public static final String CONFIGURE_ITEM_MODULE = "cim";
	public static final String NO_MODULE="NoModule";
	public static final String MODULE_FILE_EXTENSION =".ftl";
	@Autowired
	private INoticeRuleDAO noticeRuleDAO;
	@Autowired
	private IUserDAO userDAO;
	@Autowired
	private IEmailService emailService;
	@Autowired
	private IEmailTemplateService emailTemplateService;
	@Autowired
	private NoticeMessageProducer noticeMessageProducer;
	@Autowired
	private ISystemInfoDAO systemInfoDAO;
	@Autowired
	private SMSSenderHelper smsSenderHelper;
	@Autowired
	private IInstantMessageService instantmessageService;
	@Autowired
	private IProxyService proxyService;
	@Autowired
	private IUserInfoService userInfoService;
	@Autowired
	private IServerUrlService serverUrlService;
	@Autowired
	private AppContext appctx;
	@Autowired
	private PushService pushService;
	/**
	 * 通知规则分页查询
	 * 
	 * @param noticeRuleDTO
	 *            :条件查询DTO
	 * @param start
	 * @param limit
	 * @param sord
	 * @param sidx
	 * @return PageDTO
	 */
	@SuppressWarnings("unchecked")
	@Transactional
	public PageDTO findPagerNoticeRule(NoticeRuleDTO noticeRuleDTO, int start,
			int limit, String sord, String sidx) {
		PageDTO page = noticeRuleDAO.findPager(noticeRuleDTO, start, limit,
				sord, sidx);
		List<NoticeRule> entities = (List<NoticeRule>) page.getData();
		List<NoticeRuleDTO> dtos = new ArrayList<NoticeRuleDTO>(entities.size());
		for (NoticeRule entity : entities) {
			NoticeRuleDTO dto = new NoticeRuleDTO();
			NoticeRuleDTO.entity2dto(entity, dto);
			entity2dto(entity, dto);
			dtos.add(dto);
		}
		page.setData(dtos);
		return page;
	}
	/**
	 * 实体转DTO
	 * @param entity
	 * @param dto
	 */
	@Transactional
	public void  entity2dto(NoticeRule entity,NoticeRuleDTO dto){
		if (entity.getUsers() != null) {
			String userString = null;
			for (User user : entity.getUsers()) {
				if (userString == null) {
					userString = user.getLoginName();
				} else {
					userString = userString + ";" + user.getLoginName();
				}
			}
			dto.setTechnician(userString);
		}
	}
	/**
	 * 更新通知规则信息
	 * @param useStatuses
	 * @param noticeRuleNos
	 * @param url
	 */
	@Transactional
	public void updateNoticeRule(Map<String, Boolean> useStatuses,
			Map<String, String> noticeRuleNos, String url) {
		for (String key : noticeRuleNos.keySet()) {
			NoticeRule noticeRule = noticeRuleDAO.findUniqueBy("noticeRuleNo",
					key);
			if (useStatuses != null && useStatuses.size() > 0
					&& useStatuses.get(key) != null) {
				noticeRule.setUseStatus(useStatuses.get(key));
			} else {
				noticeRule.setUseStatus(false);
			}
			noticeRule.setUrl(url);
			noticeRuleDAO.update(noticeRule);
		}
	}
	
	/**
	 * 生成通知内容
	 * @param emailTemplatesDTO
	 * @param templatesType
	 *            模板类型(email,title,im,sms)
	 * @return String
	 */
	@Transactional
	private String generationNoticeContent(NoticeSendDTO noticeSendDTO,
			String templatesType) {
		String templateContent = "";
		if (noticeSendDTO != null) {
			String templateFileDir = getFilePath(noticeSendDTO.getTenantId(),noticeSendDTO.getTemplatePath());
			String templateFile = getTemplateFilePath(noticeSendDTO.getNoticeRuleNo(),noticeSendDTO.getModule(), templatesType);
			templateContent = emailTemplateService.template(noticeSendDTO,templateFileDir, templateFile,noticeSendDTO.getTenantId());
		}
		return templateContent;
	}

	/**
	 * 添加接收地址
	 * 
	 * @param email
	 *            邮件地址
	 * @param loginName
	 *            登录名
	 * @param moblie
	 *            电话
	 * @param emailReceiveAddress
	 *            邮件地址
	 * @param imReceiveUser
	 *            登录名
	 * @param smsReceiveNumber
	 *            电话
	 */
	private void addSendReceiveAddress(Set<User> allUser,
			Set<String> emailReceiveAddress, Set<String> imReceiveUser,
			Set<String> smsReceiveNumber,Set<String> pushReceiveUser) {
		if (allUser != null) {
			for (User user : allUser) {
				if(user!=null){
					if (StringUtils.hasText(user.getEmail())) {
						emailReceiveAddress.add(user.getEmail());
					}
					if (StringUtils.hasText(user.getLoginName())) {
						imReceiveUser.add(user.getLoginName());
						pushReceiveUser.add(user.getLoginName());
					}
					if (StringUtils.hasText(user.getMoblie())) {
						smsReceiveNumber.add(user.getMoblie());
					}
				}
				
			}
		}
	}
	/**
	 * 查询组下的用户
	 * @return List<User>
	 */
	@SuppressWarnings("unchecked")
	private List<User> findOrgUsers(Organization org){
		UserQueryDTO qdto = new UserQueryDTO();
		qdto.setStart(0);
		qdto.setLimit(1000);
		qdto.setBelongsGroupIds(new Long[] { org.getOrgNo() });
		PageDTO pagesDTO = userDAO.findPager(qdto, "desc",
				"userId");
		List<User> userList = (List<User>) pagesDTO
				.getData();
		return userList;
	}
	/**
	 * 设置固定通知人员
	 * @param noticeRule
	 * @param allUser
	 */
	private void addNoticeFixedUser(NoticeRule noticeRule,NoticeInfoDTO noticeInfoDto,Set<User> allUser,Set<String> emailReceiveAddress){
		// 通知规则设定的指定用户
		if (noticeRule.getUsers() != null) {
			for (User users : noticeRule.getUsers()) {
				allUser.add(users);
			}
		}
		// 通知规则设定的指定邮箱地址
		if(StringUtils.hasText(noticeInfoDto.getEmailAddress())){
			noticeInfoDto.setEmailAddress(noticeInfoDto.getEmailAddress()
					.replaceAll(",", ";"));
			String[] strs = noticeInfoDto.getEmailAddress().split(";");
			for (String str : strs) {
				emailReceiveAddress.add(str);
			}
		}
		if (StringUtils.hasText(noticeRule.getEmailAddress())) {
			noticeRule.setEmailAddress(noticeRule.getEmailAddress()
					.replaceAll(",", ";"));
			String[] strs = noticeRule.getEmailAddress().split(";");
			for (String str : strs) {
				emailReceiveAddress.add(str);
			}
		}
	}
	/**
	 * 通知单个用户
	 * @param noticeRule
	 * @param noticeInfoDto
	 * @param allUser
	 */
	private void noticeSingleUser(NoticeRule noticeRule,NoticeInfoDTO noticeInfoDto,Set<User> allUser){
		// 规则种类(请求人或报告人-requester、升级到负责人-owner、拥有者-ciOwner、使用人-ciUse)
		User user = new User();
		if (noticeRule.getNoticeRuleType().indexOf("requester") != -1) {// 求人或报告人
			user= noticeInfoDto.getRequester();
			if(user!=null){
				allUser.add(user);
			}
		}
		if (noticeRule.getNoticeRuleType().indexOf("owner") != -1) {// 升级到负责人
			user = noticeInfoDto.getOwner();
			if(user!=null){
				allUser.add(user);
			}
		}
		if (noticeRule.getNoticeRuleType().indexOf("ciOwner") != -1) {// 拥有者
			user = noticeInfoDto.getCiOwner();
			if(user!=null){
				allUser.add(user);
			}
		}
		if (noticeRule.getNoticeRuleType().indexOf("ciUse") != -1) {// 使用人
			user = noticeInfoDto.getCiUse();
			if(user!=null){
				allUser.add(user);
			}
		}
	}
	/**
	 * 通知多个用户
	 * @param noticeRule
	 * @param noticeInfoDto
	 * @param allUser
	 */
	private void noticeMultipleUsers(NoticeRule noticeRule,NoticeInfoDTO noticeInfoDto,Set<User> allUser){
		//规则种类(指派的技术组-technicalGroup、指派的技术员-technician、流程任务指派组和技术员-taskGroupAndTechnician)
		if (noticeRule.getNoticeRuleType().indexOf("technician") != -1) {// 指派的技术员
			User technician = noticeInfoDto.getAssignTechnician();
			if(technician != null){
				allUser.add(technician);
				//代理人
				if (proxyService.findProxyOrlogin(getLoginUserName(),technician.getLoginName())) {
					User proxy = userDAO.findUserByLoginName(getLoginUserName());
					allUser.add(proxy);
				}
			}
		}
		if (noticeRule.getNoticeRuleType().indexOf("technicalGroup") != -1) {// 指派的技术组
			Organization org = noticeInfoDto.getAssignOrg();
			if (org != null) {
				List<User> userList = findOrgUsers(org);
				for (User users : userList) {
					allUser.add(users);
				}
			}
		}
		if (noticeRule.getNoticeRuleType().indexOf("taskGroupAndTechnician") != -1) {// 流程任务指派组和技术员
			// 如果指派给到指定技术员了，那么不需要再通知组了
			if (noticeInfoDto.getTaskAssignTechnician() != null) {
				User taskAssignTechnician = noticeInfoDto.getTaskAssignTechnician();
				allUser.add(taskAssignTechnician);
			} else if (noticeInfoDto.getTaskAssignOrg() != null) {
				List<User> userList = findOrgUsers(noticeInfoDto.getTaskAssignOrg());
				for (User users : userList) {
					allUser.add(users);
				}
			}
		}
		if (noticeRule.getNoticeRuleType().indexOf("taskTechnicalGroupLeader") != -1) {//通知指派组组长
			Organization org=noticeInfoDto.getAssignOrg();
			if(org!=null){
				User user=org.getPersonInCharge();
				if(user!=null){
					allUser.add(user);
				}
			}
			
		}
		
	}
	/**
	 * 设置通知对象对应人员
	 * @param noticeRule
	 * @param noticeInfoDto
	 * @param allUser
	 */
	private void addNoticeRuleTypeUser(NoticeRule noticeRule,NoticeInfoDTO noticeInfoDto,Set<User> allUser){
		if (StringUtils.hasText(noticeRule.getNoticeRuleType())) {
			//通知单个用户
			noticeSingleUser(noticeRule, noticeInfoDto, allUser);
			//通知多个用户
			noticeMultipleUsers(noticeRule, noticeInfoDto, allUser);
		}
	}
	/**
	 * 设置流程对应人员
	 * @param noticeInfoDto
	 * @param allUser
	 */
	private void addProcessUser(NoticeInfoDTO noticeInfoDto,Set<User> allUser){
		// 要通知的用户
		if (noticeInfoDto.getNoticeUsers() != null) {
			for (User users : noticeInfoDto.getNoticeUsers()) {
				allUser.add(users);
			}
		}
		// 要通知的组成员
		if (noticeInfoDto.getNoticeOrgs() != null) {
			for (Organization org : noticeInfoDto.getNoticeOrgs()) {
				List<User> userList = findOrgUsers(org);
				for (User users : userList) {
					allUser.add(users);
				}
			}
		}
	}
	/**
	 * 所有的发送消息的地址
	 * @param noticeRule
	 * @param emailReceiveAddress
	 * @param imReceiveUser
	 * @param smsReceiveNumber
	 */
	private void addAllReceiveAddress(NoticeRule noticeRule,NoticeInfoDTO noticeInfoDto,
			Set<String> emailReceiveAddress, Set<String> imReceiveUser,
			Set<String> smsReceiveNumber,Set<String> pushReceiveUser){
		Set<User> allUser = new HashSet<User>();
		//设置固定通知人员
		addNoticeFixedUser(noticeRule,noticeInfoDto, allUser, emailReceiveAddress);
		//设置通知对象对应人员
		addNoticeRuleTypeUser(noticeRule, noticeInfoDto, allUser);
		//设置流程对应人员
		addProcessUser(noticeInfoDto, allUser);
		//根据人员信息设置发送地址
		addSendReceiveAddress(allUser, emailReceiveAddress,
				imReceiveUser, smsReceiveNumber,pushReceiveUser);
		
		
	}
	

	/**
	 * 邮件通知
	 * @param noticeRule
	 * @param emailTemplatesDTO
	 * @param emailReceiveAddress
	 *//*
	private void mailCommonNotice(NoticeRule noticeRule ,EmailTemplatesDTO emailTemplatesDTO,Set<String> emailReceiveAddress){
		if (noticeRule.getMailNotice()) {
			String title = "Email Send";
			StringBuffer content = new StringBuffer();
			content.append("Email Subject：").append( noticeRule.getNoticeRuleName() ).append("；Recipients：").append( emailReceiveAddress.toString() );
			String creator = "system";
			addMqInfo(emailTemplatesDTO, title, content.toString(), creator);
			try {
				emailMessageProducer.send(emailTemplatesDTO);
			} catch (Exception e) {
				e.printStackTrace();
				LOGGER.error(e);
			}
		}
	}
	*//**
	 * 短信通知
	 * @param noticeRule
	 * @param emailTemplatesDTO
	 * @param smsReceiveNumber
	 *//*
	private void smsCommonNotice(NoticeRule noticeRule ,EmailTemplatesDTO emailTemplatesDTO,Set<String> smsReceiveNumber){
		if (noticeRule.getSmsNotice()) {
			String title = "SMS Send";
			StringBuffer content = new StringBuffer();
			content.append("SMS Content：").append(noticeRule.getEmailTemp()).append("；Recipients：").append( smsReceiveNumber.toString() );
			String creator = "system";
			addMqInfo(emailTemplatesDTO, title, content.toString(), creator);
			for (String str : emailTemplatesDTO.getSmsReceiveNumber()) {
				String smsContent = generationNoticeContent(
						emailTemplatesDTO,
						NoticeRuleService.SMS_TEMPLATE_STYPE);// 短信内容
				// 调用方法，发送短信
				try {
					smsSenderHelper.SendSms(str, smsContent, true, true);
				} catch (Exception e) {
					LOGGER.error(e);
				}
			}
		}
	}
	*//**
	 * IM通知
	 * @param noticeRule
	 * @param emailTemplatesDTO
	 *//*
	private void imCommonNotice(NoticeRule noticeRule ,EmailTemplatesDTO emailTemplatesDTO){
		if (noticeRule.getImNotice()) {
			imNotice(emailTemplatesDTO);
		}
	}*/
	
	/**
	 * 获取操作者的全名，并放入Variables
	 */
	private NoticeInfoDTO getOperatorFullName(NoticeInfoDTO noticeInfoDto){
		Object obj = noticeInfoDto.getVariables();
		if(obj!=null){
			try {
				String operator ="system";
				String currentLoginName = appctx.getCurrentLoginName();
				if(StringUtils.hasText(operator)){
					User user = userDAO.findUniqueBy("loginName", currentLoginName);
					if(user!=null){
						operator = user.getFullName();
					}
				}
				BeanUtils.setProperty(obj, "operator", operator);
				noticeInfoDto.setVariables(obj);
			} catch (Exception e) {
				e.printStackTrace();
				LOGGER.error(e);
			}
		}
		return noticeInfoDto;
	}
	
	/**
	 * 通知
	 * @param noticeInfoDto  通知信息DTO
	 */
	@Transactional
	public void commonNotice(NoticeInfoDTO noticeInfoDto) {
		// 根据编号获取通知规则详细信息
		NoticeRule noticeRule = noticeRuleDAO.findUniqueBy("noticeRuleNo",noticeInfoDto.getNoticeRuleNo());
		if (noticeRule == null && noticeInfoDto.getNoticeRuleId() != null) {
			noticeRule = noticeRuleDAO.findById(noticeInfoDto.getNoticeRuleId());
		}
		if (noticeRule != null && noticeRule.getUseStatus()) {// 判断此通知规则是否已启用
			// 邮件接收的地址
			Set<String> emailReceiveAddress = new HashSet<String>();
			// IM接收的用户
			Set<String> imReceiveUser = new HashSet<String>();
			// 短信接收的手机号码
			Set<String> smsReceiveNumber = new HashSet<String>();	
			// client
			Set<String> pushMessages = new HashSet<String>();	
			//添加接收地址
			addAllReceiveAddress(noticeRule, noticeInfoDto, emailReceiveAddress, imReceiveUser, smsReceiveNumber,pushMessages);
			
			// 邮件模板变量DTO
			/*EmailTemplatesDTO emailTemplatesDTO = new EmailTemplatesDTO();
			//赋值EmailTemplatesDTO
			setEmailTemplatesDTO(emailTemplatesDTO, noticeRule, noticeInfoDto, emailReceiveAddress, imReceiveUser, smsReceiveNumber);
			// 邮件通知
			mailCommonNotice(noticeRule, emailTemplatesDTO, emailReceiveAddress);
			// 短信通知
			smsCommonNotice(noticeRule, emailTemplatesDTO, smsReceiveNumber);
			// IM通知
			imCommonNotice(noticeRule, emailTemplatesDTO);*/
			//pushNotice(noticeRule,emailTemplatesDTO,pushMessages );
			
			noticeInfoDto.setNoticeRuleNo(noticeRule.getNoticeRuleNo());
			// 通知变量DTO
			NoticeSendDTO noticeSendDTO = setNoticeSendDTO(noticeRule.getModule(),noticeInfoDto);
			// 邮件通知
			NoticeMessageProducerSend(noticeRule.getMailNotice(), noticeSendDTO, emailReceiveAddress, NoticeType.EmailNotice.getValue());
			// 短信通知
			NoticeMessageProducerSend(noticeRule.getSmsNotice(), noticeSendDTO,smsReceiveNumber, NoticeType.SMSNotice.getValue());
			// IM通知
			NoticeMessageProducerSend(noticeRule.getImNotice(), noticeSendDTO, imReceiveUser, NoticeType.IMNotice.getValue());
			// push通知
			NoticeMessageProducerSend(noticeRule.getPushNotice(), noticeSendDTO, pushMessages, NoticeType.PUSHNotice.getValue());
		}
	}
	/**
	 * 消息发送
	 * @param isNotice
	 * @param noticeSendDTO
	 * @param sendTo
	 * @param noticeType
	 */
	private void NoticeMessageProducerSend(Boolean isNotice,NoticeSendDTO noticeSendDTO,Set<String> sendTo,String noticeType){
		if (isNotice) {
			noticeSendDTO.setSendType(noticeType);
			noticeSendDTO.setSendTo(sendTo);
			try {
				noticeMessageProducer.send(noticeSendDTO);
			} catch (Exception e) {
				LOGGER.error(e);
			}
			
		}
	}
	/**
	 * 构造noticeSendDTO
	 * @param noticeInfoDto
	 * @param emailReceiveAddress
	 * @param imReceiveUser
	 * @param smsReceiveNumber
	 * @return noticeSendDTO
	 */
	private NoticeSendDTO setNoticeSendDTO(String module,NoticeInfoDTO noticeInfoDto){
		NoticeSendDTO noticeSendDTO = new NoticeSendDTO();
		getOperatorFullName(noticeInfoDto);
		noticeSendDTO.setVariables(noticeInfoDto.getVariables());
		noticeSendDTO.setTenantId(appctx.getCurrentTenantId());
		noticeSendDTO.setNoticeRuleNo(noticeInfoDto.getNoticeRuleNo());
		noticeSendDTO.setModule(module);
		//在生产之前获取path
		String path = AppConfigUtils.getInstance().getConfigPathByTenantId("templateFile", "emailTemplates",appctx.getCurrentTenantId());
		noticeSendDTO.setTemplatePath(path);
		return noticeSendDTO;
	}
	/**
	 * 查询系统用户
	 * 
	 * @return String
	 */
	public String getLoginUserName() {
		return appctx.getCurrentLoginName();
	}

	/**
	 * 邮件发送
	 * 
	 * @param noticeSendDTO
	 *            变量DTO
	 */
	@Transactional
	public void sendEmail(NoticeSendDTO noticeSendDTO) {
		if(noticeSendDTO!=null){
			MessageConsumerDTO messageConsumerDTO = new MessageConsumerDTO();
			messageConsumerDTO.setSubject(generationNoticeContent(noticeSendDTO,NoticeRuleService.TITLE_TEMPLATE_STYPE));
			messageConsumerDTO.setContent(generationNoticeContent(noticeSendDTO,NoticeRuleService.EMAIL_TEMPLATE_STYPE));
			if(noticeSendDTO.getVariables()!=null){
				try {
					messageConsumerDTO.setModule(BeanUtils.getNestedProperty(noticeSendDTO.getVariables(), "eventCode"));
				} catch (Exception e) {
					LOGGER.error(e);
				}
			}
			messageConsumerDTO.setTo(noticeSendDTO.getSendTo());
			emailService.sendMail(messageConsumerDTO);
		}
		
	}
	/**
	 * 消息发送 
	 * @param noticeSendDTO
	 */
	@Transactional
	public void sendIM(NoticeSendDTO noticeSendDTO) {
		if(noticeSendDTO!=null){
			MessageConsumerDTO messageConsumerDTO = new MessageConsumerDTO();
			String imContent = generationNoticeContent(noticeSendDTO,NoticeRuleService.IM_TEMPLATE_STYPE);
			messageConsumerDTO.setSubject(imContent);
			messageConsumerDTO.setContent(imContent);
			messageConsumerDTO.setTo(noticeSendDTO.getSendTo());
			if(noticeSendDTO.getVariables()!=null){
				messageConsumerDTO.setModule(noticeSendDTO.getVariables().getClass().getName());
				messageConsumerDTO.setRelateEno(getMessageConsumerIMRelateEno(noticeSendDTO));
			}
			instantmessageService.sendIM(messageConsumerDTO);
		}
	}
	/**
	 * get MessageConsumerDTO  IM RelateEno
	 * @param noticeSendDTO
	 * @return Long
	 */
	private Long getMessageConsumerIMRelateEno(NoticeSendDTO noticeSendDTO){
		Long relateEno = null;
		String eno = "";
		String ciId = "";
		try {
			eno = BeanUtils.getProperty(noticeSendDTO.getVariables() , "eno");
		} catch (IllegalAccessException e) {
			LOGGER.error("Im notice get property eno error"+e.getMessage());
		} catch (InvocationTargetException e) {
			LOGGER.error("Im notice get property eno error"+e.getMessage());
		} catch (NoSuchMethodException e) {
			LOGGER.error("Im notice get property eno error"+e.getMessage());
		}
		try {//如果是配置项则获取的值是ciId
			ciId = BeanUtils.getProperty(noticeSendDTO.getVariables() , "ciId");
		} catch (IllegalAccessException e) {
			LOGGER.error("Im notice get property eno error"+e.getMessage());
		} catch (InvocationTargetException e) {
			LOGGER.error("Im notice get property eno error"+e.getMessage());
		} catch (NoSuchMethodException e) {
			LOGGER.error("Im notice get property eno error"+e.getMessage());
		}
		if(StringUtils.hasText(eno)){
			relateEno = Long.parseLong(eno);
		}else if(StringUtils.hasText(ciId)){
			relateEno = Long.parseLong(ciId);
		}
		return relateEno;
	}
	
	/**
	 * 发送信息.
	 * @param noticeSendDTO 
	 * @return SMSMessageDTO
	 */
	public void sendSms(NoticeSendDTO noticeSendDTO){
		MessageConsumerDTO messageConsumerDTO = new MessageConsumerDTO();
		String smsContent = generationNoticeContent(noticeSendDTO,NoticeRuleService.SMS_TEMPLATE_STYPE);// 短信内容
		messageConsumerDTO.setSubject(smsContent);
		messageConsumerDTO.setContent(smsContent);
		messageConsumerDTO.setTo(noticeSendDTO.getSendTo());
		smsSenderHelper.sendSms(messageConsumerDTO);
	}
	/**
	 * 推送消息通知
	 */
	public void sendPush(NoticeSendDTO noticeSendDTO) {
		if (noticeSendDTO != null && noticeSendDTO.getSendTo().size() > 0) {
			
			String content = generationNoticeContent(noticeSendDTO,
					NoticeRuleService.PUSH_TEMPLATE_STYPE);// 推送内容
			Set<PushMessageDTO> pushMessages =new HashSet<PushMessageDTO>();
			String eno = "";
			if(noticeSendDTO.getVariables()!=null){
				try {
					eno = BeanUtils.getProperty(noticeSendDTO.getVariables() , "eno");
				} catch (Exception e) {
					LOGGER.error(e);
				}
			}
			for (String to: noticeSendDTO.getSendTo()) {
				User user = userDAO.findUniqueBy("loginName", to);
				PushMessageDTO dto=PushMessageDTO.user2PushMessageDTO(user);
				if(dto!=null){
					dto.setTimeStamp(new Date().getTime()+"");
					dto.setContent(content);
					dto.setEno(eno);
					pushMessages.add(dto);
				}
			}
			pushService.pushMessage(pushMessages);
		}
		
	}
	
	/**
	 * 取得FreeMaker模板文件全局加载时所需要加载的文件路径
	 * 
	 * @return FilePath
	 */
	@Transactional
	private String getFilePath(String tenantId,String path) {
		StringBuffer sb = new StringBuffer();
		if(!StringUtils.hasText(path)){
			path = AppConfigUtils.getInstance().getConfigPathByTenantId("templateFile", "emailTemplates",tenantId);
		}
		sb.append(path);
		List<SystemInfo> systemInfos = systemInfoDAO.findAll();
		if (systemInfos != null && systemInfos.size() > 0) {
			sb.append("/" + systemInfos.get(0).getSystemDataVer());
		}
		return sb.toString();
	}
	/**
	 * 邮件发送
	 * 
	 * @param emailTemplatesDTO
	 *            变量DTO
	 *//*
	public void startSendEmail(EmailTemplatesDTO emailTemplatesDTO) {
		if(emailTemplatesDTO!=null){
			EmailDTO emailDTO = new EmailDTO();
			emailDTO.setSubject(generationNoticeContent(emailTemplatesDTO,
					NoticeRuleService.TITLE_TEMPLATE_STYPE));
			emailDTO.setContent(generationNoticeContent(emailTemplatesDTO,
					NoticeRuleService.EMAIL_TEMPLATE_STYPE));
			List<String> email = new ArrayList<String>();
			for (String str : emailTemplatesDTO.getEmailReceiveAddress()) {
				email.add(str);
			}
			if(emailTemplatesDTO.getVariables()!=null){
				try {
					emailDTO.setModuleCode(BeanUtils.getNestedProperty(emailTemplatesDTO.getVariables(), "eventCode"));
				} catch (Exception e) {
					LOGGER.error(e);
				}
			}
			emailDTO.setTo(email);
			try {
				emailService.sendMail(emailDTO);
			} catch (Exception e) {
				LOGGER.error(e);
			}
		}
	}*/

/*	*//**
	 * SMS通知
	 * 
	 * @param module
	 *            模块
	 * @param emailTemplatesDTO
	 *            变量DTO
	 *//*
	public void smsNotice(EmailTemplatesDTO emailTemplatesDTO, String module) {
		for (String str : emailTemplatesDTO.getSmsReceiveNumber()) {
			String smsContent = generationNoticeContent(emailTemplatesDTO,
					NoticeRuleService.SMS_TEMPLATE_STYPE);// 短信内容
			// 调用方法，发送短信
			smsSenderHelper.SendSms(str, smsContent, true, true);
		}
	}*/


	/**
	 * 获取文件路径
	 * 
	 * @param fileName
	 *            命名
	 * @param module
	 *            模块
	 * @param templatesType
	 *            模板类型(email,title,im,sms)
	 * @return FilePath
	 */
	@Transactional
	public String getFilePath(String fileName, String module,
			String templatesType) {
		StringBuffer sb = new StringBuffer();
		sb.append(TEMPLATES_FILE_PATH);
		List<SystemInfo> systemInfos = systemInfoDAO.findAll();
		if (systemInfos != null && systemInfos.size() > 0)
			sb.append("/" + systemInfos.get(0).getSystemDataVer());
		if (StringUtils.hasText(module) && !NO_MODULE.equals(module))
			sb.append("/" + module);
		if (StringUtils.hasText(fileName))
			sb.append("/" + fileName);
		if (StringUtils.hasText(templatesType))
			sb.append("_" + templatesType);
		sb.append(MODULE_FILE_EXTENSION);
		return sb.toString();
	}


	/**
	 * 取得模板的名字
	 * 
	 * @param fileName
	 *            命名
	 * @param module
	 *            模块
	 * @param templatesType
	 *            模板类型(email,title,im,sms)
	 * @return String
	 */
	@Transactional
	public String getTemplateFilePath(String fileName, String module,
			String templatesType) {
		StringBuffer sb = new StringBuffer();
		if (StringUtils.hasText(module) && !NO_MODULE.equals(module))
			sb.append(module);
		if (StringUtils.hasText(fileName))
			sb.append("/" + fileName);
		if (StringUtils.hasText(templatesType))
			sb.append("_" + templatesType);
		sb.append(MODULE_FILE_EXTENSION);
		return sb.toString();
	}

	/**
	 * 获取模板文件内容
	 */
	public String getTempplatesFileContent(String fileName, String module,
			String templatesType) {
		if (StringUtils.hasText(fileName)) {
			File file = new File(getFilePath(fileName, module, templatesType));
			try {
				return FileUtils.readFileToString(file,"UTF-8");
			} catch (IOException e1) {
				LOGGER.error("FileUtils.readFileToString error" + e1);
				return null;
			}
		} else {
			throw new ApplicationException("ERROR_FILENAME_NULL","ERROR_FILENAME_IS_NULL");
		}

	}

	/**
	 * 以指定的始末位置从字节数组中获取其子数组
	 * 
	 * @param bt
	 *            原始字节数组
	 * @param start
	 *            起始位置
	 * @param end
	 *            结束位置
	 * @return 子字节数组
	 */
	private static byte[] getSubBytes(byte[] bt, int start, int end) {
		int size = end - start;
		byte[] result = new byte[size];
		for (int i = 0; i < size; i++) {
			result[i] = bt[i + start];
		}
		return result;
	}

	/**
	 * 
	 * 将指定的文本内容写入到指定路径的文件
	 * 
	 * @param filename
	 *            文件名称
	 * @param module
	 *            模块
	 * @param templatesType
	 * @param content
	 *            需要写入的内容
	 * @return 写入结果 boolean
	 */
	public boolean writeToFile(String filename, String module, String templatesType, String content) {
		String path = getFilePath(filename, module, templatesType);
		if (StringUtils.hasText(path)) {
			final int CACHE = 1024;
			boolean result = false;
			FileOutputStream outFile = null;
			FileChannel channel = null;
			// 将字符串转换为字节数组
			byte[] bt = null;
			try {
				bt = ("<#escape x as x!>"+content+"</#escape>").getBytes("UTF-8");
			} catch (UnsupportedEncodingException e1) {
				LOGGER.error(e1);
			}
			ByteBuffer buf = null;
			try {
				outFile = new FileOutputStream(path);
				channel = outFile.getChannel();
				// 以指定的缓存分隔字节数组，得到缓存次数
				int size = bt.length / CACHE;
				// 得到被缓存分隔后剩余的字节个数
				int mod = bt.length % CACHE;
				int start = 0;
				int end = 0;
				for (int i = 0; i < size + 1; i++) {
					if (i == size) {
						if (mod > 0) {
							// 分配新的字节缓冲区
							buf = ByteBuffer.allocate(mod);
							start = end;
							end += mod;
						} else {
							break;
						}
					} else {
						// 分配新的字节缓冲区
						buf = ByteBuffer.allocate(CACHE);
						start = end;
						end = (i + 1) * CACHE;
					}
					// 以指定的始末位置获取一个缓存大小的字节
					byte[] bytes = getSubBytes(bt, start, end);
					for (int j = 0; j < bytes.length; j++) {
						buf.put(bytes[j]);
					}
					// 反转缓冲区，为通道写入做好准备
					buf.flip();
					// 利用通道写入文件
					channel.write(buf);
					result = true;
				}
			} catch (IOException e) {
				LOGGER.error(e);
			} finally {
				// 关闭所有打开的IO流
				try {
					if(channel!=null)
						channel.close();
					if(outFile!=null)
						outFile.close();
				} catch (IOException e) {
					LOGGER.error(e);
				}
			}
			return result;
		} else {
			throw new ApplicationException("ERROR_FILENAME_NULL", "ERROR_FILENAME_IS_NULL");
		}
	}

	
	/**
	 * 模板预览所需参数
	 * 
	 * @return TemplateVariableDTO
	 */
	public Map<String, Object> request2Variable() {
		Map<String,Object> variable = new HashMap<String, Object>();
		variable.put("eventType","itsm.request(demo)");		//		templateVariableDTO.setEventType("itsm.request(demo)");
		variable.put("eno", "01L");//		templateVariableDTO.setEno(01L);
		variable.put("ecode","Ref-" +TimeUtils.format(new Date(), "yyyyMMdd") + "00001(demo)");//		templateVariableDTO.setEcode("Ref-" +TimeUtils.format(new Date(), "yyyyMMdd") + "00001(demo)");
		variable.put("etitle", "邮件预览(demo)");//		templateVariableDTO.setEtitle("邮件预览(demo)");
		variable.put("edesc", "邮件模板修改后的预览(demo)");//		templateVariableDTO.setEdesc("邮件模板修改后的预览(demo)");
		variable.put("createdOn",new Date());//		templateVariableDTO.setCreateDate(new Date());
		variable.put("solutions","解决方案详细内容(demo)");//		templateVariableDTO.setSolutions("解决方案详细内容(demo)");
		variable.put("createdByName","张三(demo)");//		templateVariableDTO.setCreatedByName("张三(demo)");
		variable.put("createdByPhone","0756-2210327(demo)");		//		templateVariableDTO.setCreatedByPhone("0756-2210327(demo)");
		variable.put("createdByEmail","WSTUO@WSTUO.com(demo)");//		templateVariableDTO.setCreatedByEmail("WSTUO@WSTUO.com(demo)");
		variable.put("ecategoryName","请求分类(demo)");//		templateVariableDTO.setEcategoryName("请求分类(demo)");
		variable.put("priorityName", "高(demo)");//		templateVariableDTO.setPriorityName("高(demo)");
		variable.put("levelName","一级：简单的咨询(demo)");//		templateVariableDTO.setLevelName("一级：简单的咨询(demo)");
		variable.put("statusName","请求新建(demo)");//		templateVariableDTO.setStatusName("请求新建(demo)");
		variable.put("technicianName", "李四(demo)");//		templateVariableDTO.setTechnicianName("李四(demo)");
		variable.put("seriousnessName", "紧急(demo)");//		templateVariableDTO.setSeriousnessName("紧急(demo)");
		variable.put("imodeName","网页表单(demo)");//		templateVariableDTO.setImodeName("网页表单(demo)");
		variable.put("assigneeGroupName", "WSTUO服务组(demo)");//		templateVariableDTO.setAssigneeGroupName("国聿服务组(demo)");
		variable.put("assigneeName", "王五(demo)");//		templateVariableDTO.setAssigneeName("王五(demo)");
		variable.put("remark","这是邮件预览功能(demo)");//		templateVariableDTO.setRemark("这是邮件预览功能(demo)");
		variable.put("ciname","lenovo服务器(demo)");//		templateVariableDTO.setCiname("lenovo服务器(demo)");
		variable.put("outcome","处理完成(demo)");//		templateVariableDTO.setOutcome("处理完成(demo)");
		variable.put("activityName","服务台(demo)");//		templateVariableDTO.setActivityName("服务台(demo)");
		variable.put("operator","赵六(demo)");//		templateVariableDTO.setOperator("赵六(demo)");
		variable.put("cino","FW-100861153(demo)");//		templateVariableDTO.setCino("FW-100861153(demo)");
		variable.put("maxCompletesTime",new Date());//		templateVariableDTO.setMaxCompletesTime(new Date());
		variable.put("maxResponsesTime",new Date());//		templateVariableDTO.setMaxResponsesTime(new Date());
		variable.put("responsesTime",new Date());//		templateVariableDTO.setResponsesTime(new Date());
		variable.put("closeTime",new Date());//		templateVariableDTO.setCloseTime(new Date());
		variable.put("closeTime",new Date());
		return variable;
	}

	/**
	 * 模板预览
	 * 
	 * @param templatesType
	 * @param writeContent
	 * @return templates html content
	 */
	public String templatePreview(String templatesType, String writeContent) {
		// 写入文件
		writeToFile("preview", null, templatesType, writeContent);
		// 读取模板文件
		
		NoticeSendDTO dto = new NoticeSendDTO();
		dto.setNoticeRuleNo("preview");
		dto.setTenantId(appctx.getCurrentTenantId());
		dto.setModule(null);
		dto.setVariables(request2Variable());

		return generationNoticeContent(dto, templatesType);
	}

	/**
	 * 加载默认通知规则
	 * @param line 解析文件后的数组
	 */
	private void loadNoticeModuledefault(String[] line){
		NoticeRule notice = new NoticeRule();
		arrayToNotice(line, notice);
		notice.setTechnicianOrEmail("0");
		noticeRuleDAO.merge(notice);
	}
	
	private void arrayToNotice(String[] line, NoticeRule notice) {
		// 规则名称
		notice.setNoticeRuleName(line[0]);
		// 规则编码
		notice.setNoticeRuleNo(line[1]);
		// 规则状态
		if ("true".equals(line[2].toString())) {
			notice.setUseStatus(true);
		} else {
			notice.setUseStatus(false);
		}
		// 通知对象
		notice.setNoticeRuleType(line[3]);
		// 邮件通知
		if ("true".equals(line[4].toString())) {
			notice.setMailNotice(true);
		} else {
			notice.setMailNotice(false);
		}
		// IM通知
		if ("true".equals(line[5].toString())) {
			notice.setImNotice(true);
		} else {
			notice.setImNotice(false);
		}
		// SMS通知
		if ("true".equals(line[6].toString())) {
			notice.setSmsNotice(true);
		} else {
			notice.setSmsNotice(false);
		}
		// 模块
		notice.setModule(line[7]);
		// 系统数据
		if ("true".equals(line[8])) {
			notice.setDataFlag((byte) 1);
		}
	}
	/**
	 * import notice data
	 * 
	 * @param importFile
	 * @return import result
	 */
	@Transactional
	public String importNotice(File importFile) {
		int insert = 0;
		int update = 0;
		int total = 0;
		int failure = 0;
		Reader rd =null;
		CSVReader reader = null;
		StringBuffer result = new StringBuffer();
		try {
			String fileEncode = FileEncodeUtils.getFileEncode(importFile);
			rd = new InputStreamReader(new FileInputStream(importFile),fileEncode);// 以字节流方式读取数据
			reader = new CSVReader(rd);
			String[] line = null;
			while ((line = reader.readNext()) != null) {
				loadNoticeModuledefault(line);
				insert++;
				total++;
			}
		} catch (IOException ex) {
			throw new ApplicationException("ERROR_CSV_FILE_IO\n" + ex, ex);
		} finally {
			try {
				if(rd!=null){
					rd.close();
				}
				if(reader!=null){
					reader.close();
				}
			} catch (IOException e) {
				LOGGER.error(e);
			}
			
		}
        
        result.append("Total:").append(total).append(",&nbsp;")
        .append("Insert:").append(insert).append(",&nbsp;")
        .append("Update:").append(update).append(",&nbsp;")
        .append("Failure:").append(failure);

        return result.toString();
	}

	/**
	 * verifi return visit
	 * 
	 * @return boolean
	 */
	public boolean verifiReturnVisit() {
		NoticeRule result = noticeRuleDAO.findUniqueBy("noticeRuleNo", "requestVisitNotice");
		return result.getUseStatus();
	}

	/**
	 * 新建一个通知规则文件
	 * 
	 * @param dto
	 *            NoticeRuleDTO
	 */
	@Transactional
	public void addNoticesRule(NoticeRuleDTO dto) {
		Long date = new Date().getTime();
		if(!StringUtils.hasText(dto.getNoticeRuleNo())){
			String noticeRuleNo = "notices_" + dto.getModule() + "_" + date;
			dto.setNoticeRuleNo(noticeRuleNo);
		}
		NoticeRule entity = new NoticeRule();
		NoticeRuleDTO.dto2entity(dto, entity);
		dto2entity(dto, entity);
		noticeRuleDAO.save(entity);
		dto.setNoticeRuleId(entity.getNoticeRuleId());
		//写入文件
		writeNoticeContentToFile(entity, dto);
	}

	/**
	 * 根据Id查找NoticeRuleDTO
	 * 
	 * @param id
	 * @return NoticeRuleDTO
	 */
	@Transactional
	public NoticeRuleDTO findById(Long id) {
		NoticeRule entity = noticeRuleDAO.findById(id);
		NoticeRuleDTO dto = new NoticeRuleDTO();
		NoticeRuleDTO.entity2dto(entity, dto);
		entity2dto(entity, dto);
		return dto;
	}
	
	/**
	 * dto转实体
	 * @param dto
	 * @param entity
	 */
	@Transactional
	public void dto2entity(NoticeRuleDTO dto,NoticeRule entity){
		if (dto.getMailNotice() == null) {
			dto.setMailNotice(false);
		}
		if (dto.getImNotice() == null) {
			dto.setImNotice(false);
		}
		if (dto.getSmsNotice() == null) {
			dto.setSmsNotice(false);
		}
		if (dto.getPushNotice() == null) {
			dto.setPushNotice(false);
		}
		entity.setMailNotice(dto.getMailNotice());
		entity.setModule(dto.getModule());
		entity.setEmailAddress(dto.getEmailAddress());
		entity.setImNotice(dto.getImNotice());
		entity.setSmsNotice(dto.getSmsNotice());
		entity.setPushNotice(dto.getPushNotice());
		entity.setNoticeRuleName(dto.getNoticeRuleName());
		entity.setNoticeRuleType(dto.getNoticeRuleType());
		entity.setUseStatus(dto.getUseStatus());
		entity.setEmailTitleTemp(dto.getNoticeRuleNo() + "_"+TITLE_TEMPLATE_STYPE+MODULE_FILE_EXTENSION);
		entity.setEmailTemp(dto.getNoticeRuleNo() + "_"+EMAIL_TEMPLATE_STYPE+MODULE_FILE_EXTENSION);
		entity.setSmsTemp(dto.getNoticeRuleNo() + "_"+SMS_TEMPLATE_STYPE+MODULE_FILE_EXTENSION);
		entity.setImTemp(dto.getNoticeRuleNo() + "_"+IM_TEMPLATE_STYPE+MODULE_FILE_EXTENSION);
		entity.setPushTemp(dto.getNoticeRuleNo() + "_"+PUSH_TEMPLATE_STYPE+MODULE_FILE_EXTENSION);
		if (StringUtils.hasText(dto.getTechnician())) {
			entity.setUsers(userInfoService.findUsersByname(dto.getTechnician()));
		}else{
			entity.setUsers(null);
		}
		entity.setTechnicianOrEmail("0");
	}

	/**
	 * 根据Id查找NoticeRuleDTO
	 * 
	 * @param id
	 * @return NoticeRule
	 */
	@Transactional
	public NoticeRule findEntityById(Long id) {
		NoticeRule entity = noticeRuleDAO.findById(id);
		return entity;
	}

	/**
	 * update notice rule
	 * 
	 * @param dto
	 *            NoticeRuleDTO
	 */
	@Transactional
	public void editNoticeMethod(NoticeRuleDTO dto) {
		NoticeRule entity = noticeRuleDAO.findById(dto.getNoticeRuleId());
		dto2entity(dto, entity);
		noticeRuleDAO.update(entity);
		//写入文件
		writeNoticeContentToFile(entity, dto);
	}
	/**
	 * 把通知内容写入文件
	 * @param entity
	 * @param dto
	 */
	private void writeNoticeContentToFile(NoticeRule entity,NoticeRuleDTO dto){
		writeToFile(entity.getNoticeRuleNo(), entity.getModule(),
				NoticeRuleService.TITLE_TEMPLATE_STYPE, dto.getEmailTitleTemp());
		writeToFile(entity.getNoticeRuleNo(), entity.getModule(),
				NoticeRuleService.EMAIL_TEMPLATE_STYPE, dto.getEmailTemp());
		writeToFile(entity.getNoticeRuleNo(), entity.getModule(),
				NoticeRuleService.SMS_TEMPLATE_STYPE, dto.getSmsTemp());
		writeToFile(entity.getNoticeRuleNo(), entity.getModule(),
				NoticeRuleService.IM_TEMPLATE_STYPE, dto.getImTemp());
		writeToFile(entity.getNoticeRuleNo(), entity.getModule(),
				NoticeRuleService.PUSH_TEMPLATE_STYPE, dto.getPushTemp());
		
	}

	/**
	 * 删除通知规则
	 * 
	 * @param nos
	 */
	@Transactional
	public void delsNoticeRules(Long[] nos) {
		for (Long no : nos) {
			NoticeRule entity = noticeRuleDAO.findById(no);
			if (entity.getDataFlag() != (byte) 1) {
				delFileFlt(getFilePath(entity.getNoticeRuleNo(),
						entity.getModule(), EMAIL_TEMPLATE_STYPE));
				delFileFlt(getFilePath(entity.getNoticeRuleNo(),
						entity.getModule(), TITLE_TEMPLATE_STYPE));
				delFileFlt(getFilePath(entity.getNoticeRuleNo(),
						entity.getModule(), IM_TEMPLATE_STYPE));
				delFileFlt(getFilePath(entity.getNoticeRuleNo(),
						entity.getModule(), SMS_TEMPLATE_STYPE));
				delFileFlt(getFilePath(entity.getNoticeRuleNo(),
						entity.getModule(), PUSH_TEMPLATE_STYPE));
			}
			noticeRuleDAO.delete(entity);
		}

	}

	/**
	 * 删除文件
	 * 
	 * @param fltPath
	 *            要删除的文件路径
	 * 
	 */
	private void delFileFlt(String fltPath) {

		File file = new File(fltPath);
		if (file.exists()) {
			file.delete();
		}
	}


	/**
	 * 根据通知编码查询实体
	 * 
	 * @param noticeName
	 *            通知编码
	 * @return NoticeEntity
	 */
	public NoticeRule findEntityByNoticeNo(String noticeName) {
		NoticeRule notice = noticeRuleDAO.findUniqueBy("noticeRuleNo",
				noticeName);
		return notice;
	}
	
	/**
	 * 审批加签通知
	 * 
	 * @param dto
	 * @param variableDTO
	 * @return boolean
	 */
	public boolean apporCountersign(NoticeRuleDTO dto, TemplateVariableDTO variableDTO) {
		NoticeSendDTO noticeSendDTO = new NoticeSendDTO();
		String tenantId = appctx.getCurrentTenantId();
		variableDTO.setTenantId(tenantId);
		noticeSendDTO.setVariables(variableDTO);
		noticeSendDTO.setTenantId(tenantId);
		noticeSendDTO.setNoticeRuleNo(dto.getNoticeRuleNo());
		noticeSendDTO.setModule(REQUEST_MODULE);
		// 邮件接收的地址
		Set<String> emailReceiveAddress = new HashSet<String>();
		emailReceiveAddress.add(dto.getTechnicianOrEmail());
		NoticeMessageProducerSend(true, noticeSendDTO, emailReceiveAddress, NoticeType.EmailNotice.getValue());
		return true;
	}

	/**
	 * 发送邮件处理流程
	 * 
	 * @param assignee
	 * @param templateVariableDTO
	 * @param flowTaskDto
	 * @param pid
	 * @param moduleType
	 */
	public void sendMailHandlingProcess(User assignee,Object variables, 
			FlowTaskDTO flowTaskDto, String moduleType) {
		if (assignee != null) {
			NoticeInfoDTO noticeInfoDto = new NoticeInfoDTO();
			noticeInfoDto.setNoticeRuleNo("sendMailHandlingProcess");
			noticeInfoDto.setVariables(setMailHandlingProcessVariables(assignee, variables, flowTaskDto, moduleType));
			noticeInfoDto.setAssignTechnician(assignee);
			commonNotice(noticeInfoDto);
		}
		
	}
	/**
	 * 构造Variables
	 * @param assignee
	 * @param variables
	 * @param flowTaskDto
	 * @param moduleType
	 * @return Object
	 */
	private Object setMailHandlingProcessVariables(User assignee,Object variables,FlowTaskDTO flowTaskDto, String moduleType){
		UserDTO ud = new UserDTO();
		ud.setUserId(assignee.getUserId());
		ud = userInfoService.setUserRandomId(ud);
		ServerUrlDTO serverUrlDTO = serverUrlService.findServiceUrl();
		try {
			BeanUtils.setProperty(variables, "outcomes", flowTaskDto.getOutcomes());
			BeanUtils.setProperty(variables, "taskId", flowTaskDto.getTaskId());
			BeanUtils.setProperty(variables, "moduleType", moduleType);
			BeanUtils.setProperty(variables, "randomParam", ud.getRandomId());
			BeanUtils.setProperty(variables, "visitPath", serverUrlDTO.getUrlName());
		} catch (Exception e) {
			LOGGER.error(e);
		} 
		return variables;
	}
	/**
	 * 根据模板文件名称查询邮件模板
	 * 
	 * @param noticeRuleDTO
	 * @return NoticeRuleDTO
	 */
	@Transactional
	public NoticeRuleDTO findByFileName(Long noticeRuleId) {
		NoticeRuleDTO noticeRuleDTO = findById(noticeRuleId);
		noticeRuleDTO = findByNoticesModel(noticeRuleDTO,
				noticeRuleDTO.getNoticeRuleNo(), noticeRuleDTO.getModule());
		return noticeRuleDTO;
	}

	/**
	 * 取得模板内容
	 * 
	 * @param noticeRuleDTO
	 * @param fileName
	 * @param module
	 * @return NoticeRuleDTO
	 */
	public NoticeRuleDTO findByNoticesModel(NoticeRuleDTO noticeRuleDTO,
			String fileName, String module) {
		String title = getTempplatesFileContent(fileName, module,
				NoticeRuleService.TITLE_TEMPLATE_STYPE);
		String content = getTempplatesFileContent(fileName, module,
				NoticeRuleService.EMAIL_TEMPLATE_STYPE);
		String sms = getTempplatesFileContent(fileName, module,
				NoticeRuleService.SMS_TEMPLATE_STYPE);
		String im = getTempplatesFileContent(fileName, module,
				NoticeRuleService.IM_TEMPLATE_STYPE);
		String push = getTempplatesFileContent(fileName, module,
				NoticeRuleService.PUSH_TEMPLATE_STYPE);
		noticeRuleDTO.setEmailTemp(content.replaceAll("<#escape x as x!>", "").replaceAll("</#escape>", ""));
		noticeRuleDTO.setEmailTitleTemp(title.replaceAll("<#escape x as x!>", "").replaceAll("</#escape>", ""));
		noticeRuleDTO.setSmsTemp(sms.replaceAll("<#escape x as x!>", "").replaceAll("</#escape>", ""));
		noticeRuleDTO.setImTemp(im.replaceAll("<#escape x as x!>", "").replaceAll("</#escape>", ""));
		noticeRuleDTO.setPushTemp(push.replaceAll("<#escape x as x!>", "").replaceAll("</#escape>", ""));
		return noticeRuleDTO;
	}

	/**消息推送的ClientId绑定
	 * @return pushBind
	 */
	@Override
	public String pushUserBind(String userName,String clientId) {
		String client = userInfoService.pushUserBind(userName, clientId);
		return client;
	}
	/**消息数量修改
	 * @return messageCount
	 */
	public int pushCount(String userName,int count) {
		return userInfoService.pushCount(userName, count);
	}
}
